package com.shanyepifu.server;

import com.shanyepifu.exception.PortllegalIIException;
import com.shanyepifu.exception.ServiceUnBindException;

import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.net.ServerSocket;
import java.net.Socket;

/**
 * Created by lifaxin on 16/7/18.
 */
public class RPCExporter {

    public void export(Object inter, int port) throws ServiceUnBindException, PortllegalIIException, IOException,
            ClassNotFoundException, NoSuchMethodException, InvocationTargetException, IllegalAccessException {

        // 判断服务是否注册
        if (inter == null) {
            throw new ServiceUnBindException("服务未绑定");
        }

        // 判断端口号是否合法
        if (!(Integer.MIN_VALUE < port && port < Integer.MAX_VALUE)) {
            throw new PortllegalIIException("端口号不合法");
        }
        // 在指定的端口上绑定Socket服务
        ServerSocket serverSocket = new ServerSocket(port);

        while (true) {
            // socket开始监听端口
            Socket socket = serverSocket.accept();
            // 获取对象输入、输出流
            ObjectInputStream ois = new ObjectInputStream(socket.getInputStream());
            ObjectOutputStream oos = new ObjectOutputStream(socket.getOutputStream());
            // 读取传过来的方法信息
            String methodName = ois.readUTF();
            Class<?>[] parameterTypes = (Class<?>[]) ois.readObject();
            Object[] arguments = (Object[]) ois.readObject();
            // 通过反射执行方法
            Method method = inter.getClass().getMethod(methodName, parameterTypes);
            Object result = method.invoke(inter, arguments);
            // 将结果返回
            oos.writeObject(result);
            oos.flush();
            // 关闭流
            oos.close();
            ois.close();
            socket.close();
        }
    }


}
